package com.mldong.modules.sys.auth.granter;

import cn.binarywang.wx.miniapp.api.WxMaService;
import cn.binarywang.wx.miniapp.bean.WxMaJscode2SessionResult;
import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.lang.Dict;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.extra.spring.SpringUtil;
import cn.hutool.log.Log;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.mldong.auth.ILoginGranter;
import com.mldong.auth.err.AuthErrEnum;
import com.mldong.base.YesNoEnum;
import com.mldong.consts.CommonConstant;
import com.mldong.exception.ServiceException;
import com.mldong.modules.sys.entity.RelThirdAccount;
import com.mldong.modules.sys.entity.User;
import com.mldong.modules.sys.mapper.RelThirdAccountMapper;
import com.mldong.modules.sys.mapper.UserMapper;
import lombok.RequiredArgsConstructor;
import me.chanjar.weixin.common.error.WxErrorException;
import org.springframework.stereotype.Component;

import java.util.List;

/**
 * 微信小程序授权
 * @author mldong
 * @date 2024/8/19
 */
@Component
@RequiredArgsConstructor
public class WxMaGranter implements ILoginGranter {
    private static final Log log = Log.get();
    private final RelThirdAccountMapper relThirdAccountMapper;
    private final UserMapper userMapper;
    @Override
    public Dict grant(Dict param) {
        String code = param.getStr("code");
        WxMaService wxMaService = SpringUtil.getBean(WxMaService.class);
        WxMaJscode2SessionResult wxMaJscode2SessionResult = null;
        try {
            wxMaJscode2SessionResult = wxMaService.getUserService().getSessionInfo(code);
        } catch (WxErrorException e) {
            log.error(e);
            ServiceException.throwBiz(AuthErrEnum.WX_AUTH_LOGIN_EX);
        }
        String openid = wxMaJscode2SessionResult.getOpenid();
        String unionid = wxMaJscode2SessionResult.getUnionid();
        User user = null;
        if(StrUtil.isNotEmpty(unionid)) {
            user = getUser(unionid, CommonConstant.WX_UNIONID);
        }
        if(user == null) {
            user = getUser(openid,CommonConstant.WX_OPENID);
        }
        if(user == null) {
            Dict data = Dict.create();
            data.put(CommonConstant.WX_OPENID,openid);
            data.put(CommonConstant.WX_UNIONID,unionid);
            ServiceException.throwBiz(AuthErrEnum.NO_REL_WX);
        }
        if(ObjectUtil.equals(user.getIsLocked(), YesNoEnum.YES)) {
            ServiceException.throwBiz(AuthErrEnum.USER_IS_LOCKED);
        }
        return BeanUtil.toBean(user,Dict.class);
    }
    public User getUser(String thirdAccount, String thirdType) {
        List<RelThirdAccount> userList = relThirdAccountMapper.selectList(
                Wrappers.lambdaQuery(RelThirdAccount.class)
                        .select(RelThirdAccount::getUserId)
                        .eq(RelThirdAccount::getThirdAccount,thirdAccount)
                        .eq(RelThirdAccount::getThirdType,thirdType)
                        .orderByDesc(RelThirdAccount::getUpdateTime)
        );
        if(CollectionUtil.isNotEmpty(userList)) {
            User user = userMapper.selectById(userList.get(0).getUserId());
            return user;
        }
        return null;
    }

}
